#include <Windows.h>
#include <tchar.h>
#include "resource.h"

#define WM_MONITOR		(WM_APP + 1001)

DWORD WINAPI ThreadProc(LPVOID lpData)
{
	HANDLE hEvents[]	= {CreateEvent(NULL, FALSE, FALSE, _T("QUIT")), CreateEvent(NULL, FALSE, FALSE, _T(""))};
	HKEY hSubKey;
	bool bQuit = false;
	
	if (ERROR_SUCCESS == RegOpenKeyEx(HKEY_CURRENT_USER,  _T("Software\\zTercelInfo"), 0, KEY_ALL_ACCESS, &hSubKey))
	{
		while (!bQuit) 
		{
			DWORD  dwFilter = REG_NOTIFY_CHANGE_NAME | REG_NOTIFY_CHANGE_ATTRIBUTES | REG_NOTIFY_CHANGE_LAST_SET | REG_NOTIFY_CHANGE_SECURITY; 
			RegNotifyChangeKeyValue(hSubKey, TRUE, dwFilter, hEvents[1], TRUE);
			DWORD dwObjID = WaitForMultipleObjects(sizeof(hEvents)/sizeof(*hEvents), hEvents, FALSE, INFINITE);
			switch (dwObjID - WAIT_OBJECT_0)
			{
				case 0:	
				{
					bQuit = true;
					break;
				}
				case 1:
				{
					HWND hWnd = (HWND)lpData;
					SendMessage(hWnd, WM_COMMAND, MAKEWPARAM(IDC_BTNREFRESH, BM_CLICK), 0);
					break;
				}
			}
		}
		for (int ii = 0; ii < sizeof(hEvents)/sizeof(*hEvents); ii++)
		{
			CloseHandle(hEvents[ii]);
		}
		
		RegCloseKey(hSubKey);
	}
	return 0;
}

int CALLBACK DlgProc(HWND hDlg, UINT nMsg, WPARAM wParam, LPARAM lParam)
{
	static DWORD nAge				= 0;
	static TCHAR szName[MAX_PATH]	= {0};
	static TCHAR szPhone[MAX_PATH]	= {0};
	static TCHAR szAddr[MAX_PATH]	= {0};
	
	switch (nMsg)
	{
		case WM_INITDIALOG:
		{
			SetWindowText(hDlg, _T("Demo0060"));
			UINT nWidth		= GetSystemMetrics(SM_CXSCREEN);
			UINT nHeight	= GetSystemMetrics(SM_CYSCREEN);
			RECT rtWindow;
			GetWindowRect(hDlg, &rtWindow);
			int  nLeft		= (nWidth - (rtWindow.right - rtWindow.left)) / 2;
			int  nRight		= (nHeight - (rtWindow.bottom - rtWindow.top)) / 2;
			SetWindowPos(hDlg, NULL, nLeft, nRight, 0, 0, SWP_NOSIZE);
	
			SendMessage(hDlg, WM_COMMAND, MAKEWPARAM(IDC_BTNREFRESH, BM_CLICK), 0);	

			SendMessage(hDlg, WM_MONITOR, 0, 0);

			break;
		}
		case WM_MONITOR:
		{
			static HANDLE hThread = NULL;
			DWORD dwStatus = 0;
			GetExitCodeThread(hThread, &dwStatus);
			if (STILL_ACTIVE != dwStatus)
			{
				CreateThread(NULL, NULL, ThreadProc, (LPVOID)hDlg, 0, NULL);
			}
			break;
		}
		case WM_COMMAND:
		{
			switch (LOWORD(wParam))
			{
				case IDC_BTNREFRESH:
				{	
					HKEY hSubKey;
					if (ERROR_SUCCESS == RegOpenKeyEx(HKEY_CURRENT_USER,  _T("Software\\zTercelInfo"), 0, KEY_ALL_ACCESS, &hSubKey))
					{
						nAge			= 0;
						_tcscpy(szName, _T(""));
						_tcscpy(szPhone, _T(""));
						_tcscpy(szAddr, _T(""));

						DWORD nType			= REG_DWORD;
						DWORD dwDataSize	= sizeof(DWORD);
						DWORD dwRet = RegQueryValueEx(hSubKey, _T("Age"), NULL, &nType, (LPBYTE)&nAge, &dwDataSize);
						
						nType			= REG_SZ;
						dwDataSize = sizeof(TCHAR) * MAX_PATH;
						RegQueryValueEx(hSubKey, _T("Name"), NULL, &nType, (LPBYTE)szName, &dwDataSize);
						
						dwDataSize = sizeof(TCHAR) * MAX_PATH;
						RegQueryValueEx(hSubKey, _T("Phone"), NULL, &nType, (LPBYTE)szPhone, &dwDataSize);

						dwDataSize = sizeof(TCHAR) * MAX_PATH;
						RegQueryValueEx(hSubKey, _T("Address"), NULL, &nType, (LPBYTE)szAddr, &dwDataSize);

						SetDlgItemInt(hDlg, IDC_EDTAGE, nAge, FALSE);
						SetDlgItemText(hDlg, IDC_EDTNAME, szName);
						SetDlgItemText(hDlg, IDC_EDTPHONE, szPhone);
						SetDlgItemText(hDlg, IDC_EDTADDR, szAddr);
						RegCloseKey(hSubKey);
					}

					break;
				}
				case IDC_BTNSAVE:
				{
					nAge = GetDlgItemInt(hDlg, IDC_EDTAGE, NULL, FALSE);
					GetDlgItemText(hDlg, IDC_EDTNAME, szName, MAX_PATH);
					GetDlgItemText(hDlg, IDC_EDTPHONE, szPhone, MAX_PATH);
					GetDlgItemText(hDlg, IDC_EDTADDR, szAddr, MAX_PATH);
					
					HKEY hSubKey;
					TCHAR szResult[MAX_PATH] = _T("Create Key Failed!");
					DWORD dwDisPis = REG_CREATED_NEW_KEY;
					if (ERROR_SUCCESS == RegCreateKeyEx(HKEY_CURRENT_USER, _T("Software\\zTercelInfo"), NULL, NULL, 0, 
						KEY_ALL_ACCESS, NULL, &hSubKey, &dwDisPis))
					{
						RegSetValueEx(hSubKey, _T("Age"), NULL, REG_DWORD, (LPBYTE)&nAge, sizeof(nAge));
						RegSetValueEx(hSubKey, _T("Name"), NULL, REG_SZ, (LPBYTE)szName, MAX_PATH);
						RegSetValueEx(hSubKey, _T("Phone"), NULL, REG_SZ, (LPBYTE)szPhone,MAX_PATH);
						RegSetValueEx(hSubKey, _T("Address"), NULL, REG_SZ, (LPBYTE)szAddr, MAX_PATH);
						RegFlushKey(hSubKey);	
						RegCloseKey(hSubKey);
						_tcscpy(szResult, _T("Save Successfully!"));
					}
			
					SetDlgItemText(hDlg, IDC_STCRES, szResult);

					SendMessage(hDlg, WM_MONITOR, 0, 0);

					break;
				}
				case IDC_BTNCLEAR:
				{
					TCHAR szResult[MAX_PATH] = _T("Delete Key Failed!");
					HKEY hSubKey;
					if (ERROR_SUCCESS == RegDeleteKey(HKEY_CURRENT_USER, _T("Software\\zTercelInfo")))
					{
						SetDlgItemText(hDlg, IDC_EDTAGE, _T(""));
						SetDlgItemText(hDlg, IDC_EDTNAME, _T(""));
						SetDlgItemText(hDlg, IDC_EDTPHONE, _T(""));
						SetDlgItemText(hDlg, IDC_EDTADDR, _T(""));

						_tcscpy(szResult, _T("Delete Successfully!"));
					}

					SetDlgItemText(hDlg, IDC_STCRES, szResult);

					break;
				}
			}

			break;
		}

		case WM_CLOSE:
		{
			HANDLE hEvent = CreateEvent(NULL, FALSE, TRUE, _T("Quit"));
			Sleep(10);
			CloseHandle(hEvent);
			PostQuitMessage(0);
			break;
		}
	}

	return 0;
}

BOOL WINAPI _tWinMain(HINSTANCE hInstance, HINSTANCE hPreInstance, LPTSTR szCmdLine, int nShowCmd)
{
	DialogBox(hInstance, MAKEINTRESOURCE(IDD_DIALOG), NULL, DlgProc);
	return 0;
}